package com.sdp.right.control;

import java.io.BufferedInputStream;
import java.io.File;
import java.io.FileInputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.text.SimpleDateFormat;
import java.util.Date;

import javax.imageio.ImageIO;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import org.springframework.beans.factory.annotation.Value;
import org.springframework.util.AntPathMatcher;
import org.springframework.util.FileCopyUtils;
import org.springframework.util.StringUtils;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import org.springframework.web.multipart.MultipartFile;
import org.springframework.web.multipart.MultipartHttpServletRequest;
import org.springframework.web.servlet.HandlerMapping;

import com.sdp.core.bizc.vo.Result;

@RestController
@RequestMapping("/SysUploadController")
public class SysUploadController {

	@Value("${sdp.filePath}")
	private String filePath;
	
	private long imageMaxSize;
	
	private long fileMaxSize;
	
	@Value("${sdp.imageMaxSize}")
	public void setImageMaxSize(long imageMaxSize) {
		this.imageMaxSize = imageMaxSize;
	}
	
	@Value("${sdp.fileMaxSize}")
	public void setFileMaxSize(long fileMaxSize) {
		this.fileMaxSize = fileMaxSize;
	}
	/**
	 * 所有系统上传的文件都存在此文件夹下
	 */
	private String sdpFiles = "sdpFiles";
	
	/**
	 * 图片上传
	 * @param request
	 * @param response
	 * @return
	 * @throws IOException
	 */
	@PostMapping(value = "/imageUp")
	public Result<?> imageUp(HttpServletRequest request, HttpServletResponse response) throws IOException {
		String dbpath = "";
		try {			
			//自定义存放的文件夹
			String customFilePath = request.getParameter("filePath");
			
			MultipartHttpServletRequest multipartRequest = (MultipartHttpServletRequest) request;
			MultipartFile mf = multipartRequest.getFile("file");// 获取上传文件对象
			if(mf.getSize()>this.imageMaxSize*1024*1024) {
				return Result.error("图片不能超过"+imageMaxSize+"兆");
			}
			if(!isImage(mf)) {
				return Result.error("只能上传图片");
			}
			
			String ofn = mf.getOriginalFilename();// 获取文件名
			String fileName = System.currentTimeMillis() + "_" + ofn;
			
			String nowMonth = new SimpleDateFormat("yyyyMM").format(new Date());
			
			// 判断文件目录是否存在
			String filePath = this.filePath+ File.separator+this.sdpFiles+File.separator+nowMonth;
			//数据库存的路径
			dbpath =  sdpFiles+File.separator+nowMonth + File.separator + fileName;
			if(!StringUtils.isEmpty(customFilePath)) {
				filePath = this.filePath + File.separator+this.sdpFiles+File.separator+customFilePath;
				dbpath = sdpFiles+File.separator+customFilePath + File.separator + fileName;
			}
			// 创建文件
			File target = new File(filePath);
			if (!target.exists()) {
				target.mkdirs();
			}

			
			String savePath = filePath + File.separator + fileName;
			File savefile = new File(savePath);
			FileCopyUtils.copy(mf.getBytes(), savefile);
			if (dbpath.contains("\\")) {
				dbpath = dbpath.replace("\\", "/");
			}

		} catch (Exception e) {
			e.printStackTrace();
			return Result.error("文件上传失败");
		}

		return Result.ok(dbpath);
	}
	
	/**
	 * 文件上传
	 * @param request
	 * @param response
	 * @return
	 * @throws IOException
	 */
	@PostMapping(value = "/fileUp")
	public Result<?> fileUp(HttpServletRequest request, HttpServletResponse response) throws IOException {
		String dbpath = "";
		try {			
			//自定义存放的文件夹
			String customFilePath = request.getParameter("filePath");
			
			MultipartHttpServletRequest multipartRequest = (MultipartHttpServletRequest) request;
			MultipartFile mf = multipartRequest.getFile("file");// 获取上传文件对象
			
			if(mf.getSize()>this.fileMaxSize*1024*1024) {
				return Result.error("文件不能超过"+fileMaxSize+"兆");
			}
			
			String ofn = mf.getOriginalFilename();// 获取文件名
			String fileName = System.currentTimeMillis() + "_" + ofn;
			
			String nowMonth = new SimpleDateFormat("yyyyMM").format(new Date());
			
			// 判断文件目录是否存在
			String filePath = this.filePath+ File.separator+this.sdpFiles+File.separator+nowMonth;
			//数据库存的路径
			dbpath =  sdpFiles+File.separator+nowMonth + File.separator + fileName;
			if(!StringUtils.isEmpty(customFilePath)) {
				filePath = this.filePath + File.separator+this.sdpFiles+File.separator+customFilePath;
				dbpath = sdpFiles+File.separator+customFilePath + File.separator + fileName;
			}
			// 创建文件
			File target = new File(filePath);
			if (!target.exists()) {
				target.mkdirs();
			}

			
			String savePath = filePath + File.separator + fileName;
			File savefile = new File(savePath);
			FileCopyUtils.copy(mf.getBytes(), savefile);
			if (dbpath.contains("\\")) {
				dbpath = dbpath.replace("\\", "/");
			}

		} catch (Exception e) {
			e.printStackTrace();
			return Result.error("文件上传失败");
		}

		return Result.ok(dbpath);
	}
	
	/**
	 * 弃用
	 * @param request
	 * @param response
	 * @return
	 * @throws IOException
	 */
	@PostMapping(value = "/up")
	public Result<?> up(HttpServletRequest request, HttpServletResponse response) throws IOException {
		String dbpath = "";
		try {			
			//自定义存放的文件夹
			String customFilePath = request.getParameter("filePath");
			
			MultipartHttpServletRequest multipartRequest = (MultipartHttpServletRequest) request;
			MultipartFile mf = multipartRequest.getFile("file");// 获取上传文件对象
			String ofn = mf.getOriginalFilename();// 获取文件名
			String fileName = System.currentTimeMillis() + "_" + ofn;
			
			String nowMonth = new SimpleDateFormat("yyyyMM").format(new Date());
			
			// 判断文件目录是否存在
			String filePath = this.filePath+ File.separator+this.sdpFiles+File.separator+nowMonth;
			//数据库存的路径
			dbpath =  sdpFiles+File.separator+nowMonth + File.separator + fileName;
			if(!StringUtils.isEmpty(customFilePath)) {
				filePath = this.filePath + File.separator+this.sdpFiles+File.separator+customFilePath;
				dbpath = sdpFiles+File.separator+customFilePath + File.separator + fileName;
			}
			// 创建文件
			File target = new File(filePath);
			if (!target.exists()) {
				target.mkdirs();
			}

			
			String savePath = filePath + File.separator + fileName;
			File savefile = new File(savePath);
			FileCopyUtils.copy(mf.getBytes(), savefile);
			if (dbpath.contains("\\")) {
				dbpath = dbpath.replace("\\", "/");
			}

		} catch (Exception e) {
			e.printStackTrace();
			return Result.error("文件上传失败");
		}

		return Result.ok(dbpath);
	}

	@GetMapping(value = "/down/**")
	public void down(HttpServletRequest request, HttpServletResponse response) throws IOException {
		// ISO-8859-1 ==> UTF-8 进行编码转换
		String filePath = extractPathFromPattern(request);
		// 其余处理略
		InputStream inputStream = null;
		OutputStream outputStream = null;
		try {
			String downloadFilePath = this.filePath+File.separator+filePath;
			File file = new File(downloadFilePath);
			if (file.exists()) {
				response.setContentType("application/force-download");// 设置强制下载不打开            
				response.addHeader("Content-Disposition","attachment;fileName=" + new String(file.getName().getBytes("UTF-8"), "iso-8859-1"));
				inputStream = new BufferedInputStream(new FileInputStream(file));
				outputStream = response.getOutputStream();
				byte[] buf = new byte[1024];
				int len;
				while ((len = inputStream.read(buf)) > 0) {
					outputStream.write(buf, 0, len);
				}
				response.flushBuffer();
			}

		} catch (Exception e) {

			e.printStackTrace();
		} finally {
			if (inputStream != null) {
				try {
					inputStream.close();
				} catch (IOException e) {
					e.printStackTrace();
				}
			}
			if (outputStream != null) {
				try {
					outputStream.close();
				} catch (IOException e) {
					e.printStackTrace();
				}
			}
		}

	}

	private static String extractPathFromPattern(final HttpServletRequest request) {
		String path = (String) request.getAttribute(HandlerMapping.PATH_WITHIN_HANDLER_MAPPING_ATTRIBUTE);
		String bestMatchPattern = (String) request.getAttribute(HandlerMapping.BEST_MATCHING_PATTERN_ATTRIBUTE);
		return new AntPathMatcher().extractPathWithinPattern(bestMatchPattern, path);
	}
	
	private static boolean isImage(MultipartFile mf) {
		try {
			ImageIO.read(mf.getInputStream());
			return true;
		}catch (IOException e) {
			return false;
		}
	}
}
